package net.lastcoder.ifserver.web;

import net.lastcoder.ifserver.Constants;

import org.apache.mina.core.buffer.IoBuffer;
import org.json.JSONException;
import org.json.JSONObject;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.util.ArrayList;

/**这是json转if packet的解析
 * auth: WenYF
 * date: 2017/3/13
 */
public class FastJsonParser {
    private static final Logger Log = LoggerFactory.getLogger(FastJsonParser.class);

    private static final String MAX_PROPERTY_NAME = "web.socket.buffer.size";
    private static final byte startTag = '{';
    private static final byte endTag= '}';

    private int maxBufferSize;

    /**
     * 将数据放在这里面
     */
    private StringBuilder buffer;

    private int tagCounter = 0;
    private boolean findHead;

    private ArrayList<String> packets;

    public FastJsonParser() {
        // 32kb
        maxBufferSize = 1024 * 32;
        buffer = new StringBuilder(maxBufferSize);
        packets = new ArrayList<>();

    }

    public void read(String message) {
        Thread thread = Thread.currentThread();
        Log.debug("thread name = " + thread.getName());
        Log.debug("message : " + message);

        for(int i = 0; i < message.length(); i++) {
            char b = message.charAt(i);
            this.buffer.append(b);

            switch (b) {
                case startTag:
                    tagCounter++;

                    if (tagCounter == 1) {
                        findHead = true;
                    }
                    break;
                case endTag:
                    tagCounter--;

                    if (tagCounter == 0 && findHead) {
                        processData();
                    }
                    break;
                default:
                    if (!findHead) {
                        // 异常
                        return;
                    }
                    break;
            }
        }
    }

    public void read(IoBuffer buffer) {
        buffer.mark();
        String dump = buffer.getHexDump();
        Thread thread = Thread.currentThread();
        Log.debug("thread name = " + thread.getName());
        Log.debug("buffer : " + dump);
        buffer.reset();

        while(buffer.remaining() > 0) {
            char b = (char) buffer.get();
            this.buffer.append(b);

            switch (b) {
                case startTag:
                    tagCounter++;

                    if (tagCounter == 1) {
                        findHead = true;
                    }
                    break;
                case endTag:
                    tagCounter--;

                    if (tagCounter == 0 && findHead) {
                        processData();
                    }
                    break;
                default:
                    if (!findHead) {
                        // 异常
                        buffer.position(buffer.limit());
                        return;
                    }
                    break;
            }
        }
    }

    private void processData() {
        String str = buffer.toString();
        packets.add(str);
        buffer.delete(0, buffer.length());
        findHead = false;
    }

    public boolean hasPacket() {
        return packets.size() > 0;
    }

    public String getPacket() {
        return packets.remove(0);
    }
}
